<template>
  <div
    ref="swiper"
    :class="[direction == 'horizontal' ? 'swiper' : 'swiper vertical']"
    @touchstart="ontouchstart"
    @touchmove="ontouchmove"
    @touchend="ontouchend"
  >
    <ul :style="style">
      <li
        :style="{ width: width + 'px' }"
        :class="{ active: curr == index }"
        v-for="(item, index) in list"
        :key="index"
      >
        <img :src="item" />
      </li>
    </ul>
    <div class="cir" v-if="direction == 'horizontal'">
      <a
        :class="{ on: curr == index }"
        href="javascript:;"
        v-for="(item, index) in list"
        :key="index"
      ></a>
    </div>
  </div>
</template>

<script>
export default {
  name: "swiper",
  data() {
    return {
      style: {},
      width: "",
      height: "",
      startX: 0,
      startY: 0,
      offset: 0,
      curr: 0,
      threshold: 50,
      duration: 300,
      count: 0,
      timer: null,
    }
  },
  props: {
    direction: {
      default: "horizontal",
    },
    list: Array,
    auto: {
      type: Boolean,
      default: false,
    },
  },
  watch: {},
  methods: {
    ontouchstart(e) {
      clearInterval(this.timer)
      this.startX = e.changedTouches[0].pageX
      this.startY = e.changedTouches[0].pageY

      this.$set(this.style, "transition", "none")
    },
    ontouchmove(e) {
      let moveX = e.changedTouches[0].pageX
      let moveY = e.changedTouches[0].pageY

      let distance = 0,
        transform = 0,
        distanceX = moveX - this.startX,
        distanceY = moveY - this.startY
      if (
        this.direction === "horizontal" &&
        Math.abs(distanceX) > Math.abs(distanceY)
      ) {
        distance = distanceX
        transform = "translate3d(" + (distance - this.offset) + "px, 0, 0)"
      } else if (
        this.direction != "horizontal" &&
        Math.abs(distanceY) > Math.abs(distanceX)
      ) {
        distance = distanceY
        transform = "translate3d(0, " + (distance - this.offset) + "px, 0)"
      } else {
        return
      }

      this.$set(this.style, "transform", transform)

      e.preventDefault()
    },
    ontouchend(e) {
      let endX = e.changedTouches[0].pageX
      let endY = e.changedTouches[0].pageY

      var distance = endY - this.startY
      if (this.direction === "horizontal") {
        distance = endX - this.startX
      }

      if (distance > this.threshold) {
        this.curr = this.curr === 0 ? 0 : --this.curr
      } else if (distance < -this.threshold) {
        this.curr = this.curr < this.count - 1 ? ++this.curr : this.curr
      }
      this.show(this.curr)
      this.timer = this.autoPlay()
    },
    show(idx) {
      this.offset = idx * this.height
      var transform = "translate3d(0, -" + this.offset + "px, 0)"

      if (this.direction === "horizontal") {
        this.offset = idx * this.width
        transform = "translate3d(-" + this.offset + "px, 0, 0)"
      }

      var duration = this.duration + "ms"

      this.$set(this.style, "transition", duration)
      this.$set(this.style, "transform", transform)
    },
    autoPlay() {
      if (this.auto) {
        return setInterval(() => {
          if (this.curr == this.count - 1) {
            this.curr = -1
          }
          this.show(++this.curr)
        }, 3000)
      }
    },
  },
  mounted() {
    this.count = this.list.length
    this.width = this.$refs.swiper.offsetWidth
    this.height = this.$refs.swiper.offsetHeight
    this.$set(this.style, "width", this.width + "px")
    if (this.direction == "horizontal") {
      this.$set(this.style, "width", this.width * this.count + "px")
    }
    // 轮播
    this.timer = this.autoPlay()
  },
}
</script>

<style lang="less" scoped>
.swiper {
  overflow: hidden;
  position: relative;
}
.swiper ul li {
  float: left;
  width: 100%;
}
.swiper ul li img {
  width: 100%;
}
.swiper .cir {
  position: absolute;
  left: 50%;
  transform: translate3d(-50%, 0, 0);
  bottom: 5px;
}
.swiper .cir a {
  display: inline-block;
  width: 10px;
  height: 10px;
  margin: 0 5px;
  background: #000;
  opacity: 0.5;
  border-radius: 50%;
}
.swiper .cir a.on {
  background: #ddd;
  opacity: 0.8;
}
/* 竖屏切换 */
.swiper.vertical,
.swiper.vertical ul,
.swiper.vertical li {
  height: 100%;
}
</style>
